#include "pch.hpp"
#include "FontModel.hpp"




FontModel::FontModel(const Document::ptr& document)
	: m_document(document)
{}
///////////////////////////////////////////////////////////////////////////////////////////////////




void FontModel::setDocument(const Document::ptr& document)
{
	if(m_document == document)
		return;

	if(m_document && m_document->styleDocument().fonts().size())
	{
		beginRemoveRows(QModelIndex(), 0, m_document->styleDocument().fonts().size() - 1);
		m_document->styleDocument().fonts().clear();
		endRemoveRows();
	}

	if(document && document->styleDocument().fonts().size())
	{
		beginInsertRows(QModelIndex(), 0, document->styleDocument().fonts().size() - 1);
		m_document = document;
		endInsertRows();
	}
	else
	{
		m_document = document;
	}
}
///////////////////////////////////////////////////////////////////////////////////////////////////

int FontModel::rowCount(const QModelIndex& parent) const
{
	return m_document ? m_document->styleDocument().fonts().size() : 0;
}
///////////////////////////////////////////////////////////////////////////////////////////////////

QVariant FontModel::data(const QModelIndex& index, int role) const
{
	if(!m_document)
		BOOSTEXT_THROW(programming_error("Non-existent model"));

	switch(role)
	{
	case Qt::DisplayRole:
		{
			const AdvancedFont& f = font(index);
			const FontDesc& desc = f.desc();
			QString d = QString("%1 %2px").arg(desc.name).arg(desc.size);

			if(desc.outline != 0)
				d += QString(", %1px outline").arg(desc.outline);

			if(desc.bold)
				d += ", bold";

			if(desc.italic)
				d +=", italic";

			return d;
		}
		break;
	}

	return QVariant();
}
///////////////////////////////////////////////////////////////////////////////////////////////////




void FontModel::add(const AdvancedFont& font)
{
	if(!m_document)
		BOOSTEXT_THROW(programming_error("Non-existent model"));

	int row = calculateRow(font);

	beginInsertRows(QModelIndex(), row, row);
	m_document->styleDocument().add(font);
	endInsertRows();
}
///////////////////////////////////////////////////////////////////////////////////////////////////

void FontModel::remove(const QModelIndex& index)
{
	if(!m_document)
		BOOSTEXT_THROW(programming_error("Non-existent model"));

	const AdvancedFont& f = font(index);

	beginRemoveRows(QModelIndex(), index.row(), index.row());
	m_document->styleDocument().remove(f.desc());
	endRemoveRows();
}
///////////////////////////////////////////////////////////////////////////////////////////////////

AdvancedFont& FontModel::font(const QModelIndex& index)
{
	if(!m_document)
		BOOSTEXT_THROW(programming_error("Non-existent model"));

	Fonts& fonts = m_document->styleDocument().fonts();

	if(index.row() >= fonts.size())
		BOOSTEXT_THROW(out_of_range_exception(index.row(), 0, fonts.size()));

	Fonts::iterator i = fonts.begin();
	std::advance(i, index.row());

	return *i;
}
///////////////////////////////////////////////////////////////////////////////////////////////////

const AdvancedFont& FontModel::font(const QModelIndex& index) const
{
	if(!m_document)
		BOOSTEXT_THROW(programming_error("Non-existent model"));

	const Fonts& fonts = m_document->styleDocument().fonts();

	if(index.row() >= fonts.size())
		BOOSTEXT_THROW(out_of_range_exception(index.row(), 0, fonts.size()));

	Fonts::const_iterator i = fonts.begin();
	std::advance(i, index.row());

	return *i;
}
///////////////////////////////////////////////////////////////////////////////////////////////////




int FontModel::calculateRow(const AdvancedFont& font) const
{
	if(!m_document)
		BOOSTEXT_THROW(programming_error("Non-existent model"));

	Fonts fonts = m_document->styleDocument().fonts();
	Fonts::iterator i = fonts.insert(font.desc(), font);

	return std::distance(fonts.begin(), i);
}
///////////////////////////////////////////////////////////////////////////////////////////////////
